<!-- 客服代表会话组件：游客列表、会话列表、聊天窗口、用户信息等 -->
<template>
    <div>
        <el-row class="chat-row height-100" :gutter="15">
            <el-col class="height-100" :span="4">
                <div class="chat-col-box left-box">
                    <div class="session-item csr-box">
                        <img class="avatar" :src="fullUrl(kefu.state.userInfo.avatar)" />
                        <div class="session-info csr-info">
                            <div class="nickname">{{ kefu.state.userInfo.nickname }}</div>
                            <el-dropdown>
                                <div class="my-status">
                                    <div class="status-dot" :class="'status-' + kefu.state.userInfo.status">●</div>
                                    <div class="status-text">{{ getStatusText(kefu.state.userInfo.status) }}</div>
                                    <icon size="12" color="var(--el-text-color-regular)" name="el-icon-CaretBottom" />
                                </div>
                                <template #dropdown>
                                    <el-dropdown-menu>
                                        <el-dropdown-item class="my-status" @click="onCsrStatusChange('online')">
                                            <div class="status-dot status-online">●</div>
                                            <div class="status-text">在线</div>
                                        </el-dropdown-item>
                                        <el-dropdown-item class="my-status" @click="onCsrStatusChange('busy')">
                                            <div class="status-dot status-busy">●</div>
                                            <div class="status-text">忙碌</div>
                                        </el-dropdown-item>
                                        <el-dropdown-item class="my-status" @click="onCsrStatusChange('invisible')">
                                            <div class="status-dot status-invisible">●</div>
                                            <div class="status-text">隐身</div>
                                        </el-dropdown-item>
                                        <el-dropdown-item divided class="my-status" @click="onCsrStatusChange('offline')">
                                            <div class="status-dot status-offline">●</div>
                                            <div class="status-text">离线</div>
                                        </el-dropdown-item>
                                    </el-dropdown-menu>
                                </template>
                            </el-dropdown>
                        </div>
                    </div>
                    <template v-if="kefu.state.touristData.length > 0">
                        <div class="tourist-list ba-scroll-style">
                            <div
                                v-for="(tourist, index) in kefu.state.touristData"
                                :key="index"
                                @click="kefu.activeSession('tourist', tourist)"
                                @contextmenu.prevent="onActiveContextmenu('tourist', tourist, $event)"
                                class="session-item tourist-item"
                                :class="kefu.state.activeTourist == tourist.id ? 'active' : ''"
                            >
                                <div class="session-info tourist-info">
                                    <div class="title-box">
                                        <div class="nickname">{{ tourist.nickname }}</div>
                                        <div :class="'status-' + tourist.status" class="date-time">{{ getStatusText(tourist.status) }}</div>
                                    </div>
                                    <div class="other">
                                        <span v-if="tourist.last_message">
                                            {{ tourist.last_message }}
                                        </span>
                                        <span v-else :title="tourist.last_trajectory_url">
                                            浏览{{ tourist.trajectory_count }}页，正在访问 {{ tourist.last_trajectory_url }}
                                        </span>
                                    </div>
                                </div>
                            </div>
                        </div>
                    </template>
                    <el-empty v-else :image-size="40" description="暂时没有访客..." />
                </div>
            </el-col>
            <el-col class="height-100" :span="14">
                <el-row class="chat-col-box session-row" :class="kefu.state.sessionDialog.shake ? 'ba-kefu-shake' : ''">
                    <el-col class="session-list h100" :span="6">
                        <div class="session-search">
                            <el-input
                                class="search-left"
                                placeholder="搜索"
                                size="small"
                                v-model="kefu.state.sessionDialog.searchSessionKeyword"
                                prefix-icon="el-icon-Search"
                                @input="onSendSearch('session')"
                                @keyup.enter="onSendSearch('session')"
                                clearable
                            />
                            <div class="search-right">
                                <el-dropdown trigger="click">
                                    <Icon name="el-icon-Plus" size="16" color="var(--el-text-color-regular)" />
                                    <template #dropdown>
                                        <el-dropdown-menu>
                                            <el-dropdown-item @click="onAddSession">添加会话</el-dropdown-item>
                                        </el-dropdown-menu>
                                    </template>
                                </el-dropdown>
                            </div>
                            <div v-if="kefu.state.sessionDialog.searchSession" class="search-session-done ba-scroll-style">
                                <div
                                    v-for="(user, idx) in kefu.state.sessionDialog.searchData"
                                    :key="idx"
                                    class="session-item"
                                    @click="kefu.addSession(user.id)"
                                >
                                    <img class="avatar" :src="fullUrl(user.avatar)" />
                                    <div class="session-info">
                                        <div class="title-box">
                                            <span class="nickname">{{ user.nickname }}</span>
                                        </div>
                                        <div class="other">
                                            <span class="status-offline">[{{ getStatusText(user.status) }}]</span>
                                            <span :title="(user.last_login_time ? user.last_login_time : '未知') + ' ' + user.remark"
                                                >上次登录：{{ (user.last_login_time ? user.last_login_time : '未知') + ' ' + user.remark }}</span
                                            >
                                        </div>
                                    </div>
                                </div>
                                <el-empty v-if="kefu.state.sessionDialog.searchData.length <= 0" :image-size="40" description="暂无数据..." />
                            </div>
                        </div>
                        <div
                            :ref="kefu.common.sessionsRef"
                            v-if="kefu.state.sessionData.length"
                            @scroll="onSessionScroll"
                            class="sessions ba-scroll-style"
                        >
                            <div
                                v-for="(session, index) in kefu.state.sessionData"
                                :key="index"
                                class="session-item"
                                @click="kefu.activeSession('session', session)"
                                @contextmenu.prevent="onActiveContextmenu('session', session, $event)"
                                :class="[kefu.state.activeSession == session.id ? 'active' : '', session.top ? 'session-top' : '']"
                            >
                                <img class="avatar" :src="fullUrl(session.avatar)" />
                                <div class="session-info">
                                    <div class="title-box">
                                        <span class="nickname">{{ session.nickname }}</span>
                                        <span class="date-time">{{ session.sort_time }}</span>
                                    </div>
                                    <div class="title-box">
                                        <div class="other">
                                            <!-- 会话列表的用户在线时，不显示状态信息 -->
                                            <span v-if="session.session_user_status != 'online'" class="status-offline"
                                                >[{{ getStatusText(session.session_user_status) }}]</span
                                            >
                                            <span>{{ session.last_message }}</span>
                                        </div>
                                        <div v-if="session.unread_message_count" class="badge">{{ session.unread_message_count }}</div>
                                    </div>
                                </div>
                            </div>
                        </div>
                        <el-empty v-else :image-size="40" description="暂时没有会话..." />
                    </el-col>
                    <el-col class="session-window h100" :span="18">
                        <div class="session-header">
                            <div class="title">{{ isEmpty(kefu.state.sessionInfo) ? '无会话' : kefu.state.sessionInfo.nickname }}</div>
                            <Icon v-if="kefu.state.awaitResponse" name="el-icon-Loading" size="14" class="await-response-loading is-loading" />
                        </div>
                        <Window class="window-records" />
                    </el-col>
                </el-row>
            </el-col>
            <el-col class="height-100" :span="6">
                <div class="chat-col-box right-box">
                    <el-tabs stretch v-model="kefu.state.activeOptTab" @tab-change="onOptChange" class="operate-tabs h100">
                        <el-tab-pane class="operate-tabs-pane ba-scroll-style" label="基本信息" name="base">
                            <el-form
                                v-if="(kefu.state.activeSession || kefu.state.activeTourist) && !isEmpty(kefu.state.baseInfoForm)"
                                ref="baseFormRef"
                                :model="kefu.state.baseInfoForm"
                                label-position="top"
                            >
                                <el-form-item label="昵称" prop="nickname">
                                    <el-input
                                        ref="userNicknameRef"
                                        @change="onBaseInfoFormChange('nickname')"
                                        v-model="kefu.state.baseInfoForm.nickname"
                                        placeholder="称谓/姓名/备注名"
                                    />
                                </el-form-item>
                                <FormItem
                                    label="分组"
                                    type="remoteSelects"
                                    v-model="kefu.state.baseInfoForm.group_ids"
                                    prop="group_ids"
                                    :input-attr="{
                                        pk: 'group.id',
                                        field: 'name',
                                        remoteUrl: '/worker/kefu.HttpIndex/group',
                                        onChange: () => onBaseInfoFormChange('group_ids'),
                                    }"
                                    placeholder="可多选"
                                />
                                <FormItem
                                    label="绑定会员"
                                    type="remoteSelect"
                                    v-model="kefu.state.baseInfoForm.user_id"
                                    prop="user_id"
                                    :input-attr="{
                                        pk: 'user.id',
                                        field: 'nickname',
                                        remoteUrl: '/worker/kefu.HttpIndex/user',
                                        onChange: () => onBaseInfoFormChange('user_id'),
                                        emptyValues: ['', null, undefined, 0],
                                        valueOnClear: 0,
                                    }"
                                />
                                <FormItem
                                    label="联系方式"
                                    type="textarea"
                                    v-model="kefu.state.baseInfoForm.contacts"
                                    prop="contacts"
                                    :input-attr="{ rows: 3, onChange: () => onBaseInfoFormChange('contacts') }"
                                    placeholder="可用联系方式"
                                />
                                <FormItem
                                    label="来源"
                                    type="string"
                                    :input-attr="{
                                        onChange: () => onBaseInfoFormChange('referrer'),
                                    }"
                                    v-model="kefu.state.baseInfoForm.referrer"
                                    prop="referrer"
                                />
                                <FormItem
                                    label="性别"
                                    type="radio"
                                    v-model="kefu.state.baseInfoForm.gender"
                                    prop="gender"
                                    :data="{ content: { '0': '未知', '1': '男', '2': '女' } }"
                                    :input-attr="{
                                        onChange: () => onBaseInfoFormChange('gender'),
                                    }"
                                />
                                <FormItem
                                    label="公司"
                                    type="string"
                                    v-model="kefu.state.baseInfoForm.company"
                                    prop="company"
                                    :input-attr="{
                                        onChange: () => onBaseInfoFormChange('company'),
                                    }"
                                />
                                <FormItem
                                    label="职业"
                                    type="string"
                                    v-model="kefu.state.baseInfoForm.occupation"
                                    prop="occupation"
                                    :input-attr="{
                                        onChange: () => onBaseInfoFormChange('occupation'),
                                    }"
                                />
                                <FormItem
                                    label="备注"
                                    type="textarea"
                                    v-model="kefu.state.baseInfoForm.remark"
                                    prop="remark"
                                    :input-attr="{ rows: 2, onChange: () => onBaseInfoFormChange('remark') }"
                                />
                            </el-form>
                            <el-empty v-else :image-size="40" description="请选择会话或游客" />
                        </el-tab-pane>
                        <el-tab-pane class="operate-tabs-pane ba-scroll-style" @scroll="onTrajectoryScroll" label="访问轨迹" name="trajectory">
                            <el-timeline v-if="kefu.state.activeSession || kefu.state.activeTourist" class="trajectory-timeline">
                                <el-timeline-item
                                    v-for="(trajectory, index) in kefu.state.trajectorys.data"
                                    :key="index"
                                    icon="el-icon-MoreFilled"
                                    size="large"
                                    :type="getTrajectoryType(trajectory)"
                                    :hollow="true"
                                    :timestamp="trajectory.create_time"
                                >
                                    {{ getTrajectoryContent(trajectory) }}
                                </el-timeline-item>
                            </el-timeline>
                            <el-empty v-else :image-size="40" description="请选择会话或游客" />
                            <div v-if="kefu.state.trajectorys.loading" class="ba-center">
                                <Icon name="el-icon-Loading" class="is-loading" />
                            </div>
                        </el-tab-pane>
                        <el-tab-pane class="operate-tabs-pane ba-scroll-style" label="知识库" name="kbs">
                            <div>
                                <div class="kbs-match">
                                    <el-input
                                        placeholder="匹配"
                                        @input="onMatchInput"
                                        v-model="kefu.state.kbs.matchInput"
                                        prefix-icon="el-icon-MagicStick"
                                    />
                                </div>
                                <div class="kbs-list" v-if="kefu.state.kbs.data.length">
                                    <div class="kbs-item" v-for="(item, index) in kefu.state.kbs.data" :key="index">
                                        <div class="kbs-title">{{ item.title }}</div>
                                        <div class="kbs-content-box">
                                            <div class="kbs-content">
                                                {{ item.answer }}
                                            </div>
                                            <el-button @click="onSendKb(item.answer)" type="primary" size="small" class="send-button">使用</el-button>
                                        </div>
                                    </div>
                                </div>
                                <el-empty v-else :image-size="40" description="暂时没有数据..." />
                            </div>
                            <div v-if="kefu.state.kbs.loading" class="ba-center">
                                <Icon name="el-icon-Loading" class="is-loading" />
                            </div>
                        </el-tab-pane>
                    </el-tabs>
                </div>
            </el-col>
        </el-row>

        <Contextmenu
            ref="contextmenuRef"
            :width="120"
            :items="kefu.state.contextMenuType == 'tourist' ? touristContextMenus : sessionContextMenus"
            @menu-click="onActiveContextmenuItem"
        />

        <el-dialog v-model="kefu.state.sessionDialog.searchDialog" class="session-dialog" title="添加会话" width="700" draggable>
            <div class="dialog-session-search-box">
                <div class="dialog-session-search">
                    <el-input
                        @keyup.enter="onSendSearch('user')"
                        class="dialog-search-left"
                        size="large"
                        v-model="state.searchDialogKeyword"
                        prefix-icon="el-icon-Search"
                        placeholder="用户ID/昵称/绑定会员昵称"
                        ref="searchKeywordRef"
                        clearable
                    />
                    <el-button size="large" type="primary" @click="onSendSearch('user')">搜索一下</el-button>
                </div>
                <div v-if="kefu.state.sessionDialog.searchData.length" class="opts-session-list ba-scroll-style">
                    <div v-for="(item, idx) in kefu.state.sessionDialog.searchData" :key="idx" class="session-item">
                        <img class="avatar" :src="fullUrl(item.avatar)" />
                        <div class="session-info">
                            <div class="title-box">
                                <span class="nickname">{{ item.nickname }}</span>
                                <el-button @click="kefu.addSession(item.id)" type="primary" size="small">对话</el-button>
                            </div>
                            <div class="other">
                                <span class="status-offline">[{{ getStatusText(item.status) }}]</span>
                                <span :title="(item.last_login_time ? item.last_login_time : '未知') + ' ' + item.remark"
                                    >上次登录：{{ (item.last_login_time ? item.last_login_time : '未知') + ' ' + item.remark }}</span
                                >
                            </div>
                        </div>
                    </div>
                </div>
                <el-empty v-else :image-size="40" description="暂无数据..." />
            </div>
        </el-dialog>

        <el-dialog v-model="kefu.state.transfer.show" class="transfer-dialog" title="转接会话" width="700" draggable>
            <FormItem
                label="转接给"
                type="remoteSelect"
                v-model="kefu.state.transfer.csrId"
                :input-attr="{
                    pk: 'user.id',
                    field: 'nickname',
                    remoteUrl: '/worker/kefu.HttpIndex/csr',
                    params: {
                        currentCsrId: kefu.state.userInfo.id,
                    },
                    emptyValues: ['', null, undefined, 0],
                    valueOnClear: 0,
                }"
                placeholder="请选择要转接的客服代表"
            />
            <template #footer>
                <div class="ba-center">
                    <el-button @click="kefu.state.transfer.show = false">取消</el-button>
                    <el-button v-blur :loading="kefu.state.transfer.loading" @click="onTransfer" type="primary"> 确认转接 </el-button>
                </div>
            </template>
        </el-dialog>
    </div>
</template>

<script setup lang="ts">
import { ref, reactive, nextTick } from 'vue'
import { isEmpty, debounce } from 'lodash-es'
import Contextmenu from '/@/components/contextmenu/index.vue'
import Window from '/@/components/kefu/components/window.vue'
import FormItem from '/@/components/formItem/index.vue'
import { FormInstance, TabPaneName, InputInstance } from 'element-plus'
import { getStatusText } from '/@/components/kefu/store'
import { fullUrl } from '/@/utils/common'
import type kefuClass from '/@/components/kefu/index'
import useCurrentInstance from '/@/utils/useCurrentInstance'
import { ContextMenuItemClickEmitArg } from '/@/components/contextmenu/interface'

const baseFormRef = ref<FormInstance>()
const contextmenuRef = ref()
const userNicknameRef = ref<InputInstance>()
const searchKeywordRef = ref<InputInstance>()
const { proxy } = useCurrentInstance()
const kefu = proxy.kefu as kefuClass

const state = reactive({
    searchDialogKeyword: '',
})

const touristContextMenus = [
    { name: 'dialog-force', label: '强制对话', icon: 'fa fa-commenting-o' },
    { name: 'dialog-invite', label: '邀请对话', icon: 'fa fa-bell-o' },
]
const sessionContextMenus = [
    { name: 'top', label: '置顶会话', icon: 'fa fa-angle-double-up' },
    { name: 'transfer', label: '转接会话', icon: 'fa fa-share-alt' },
    { name: 'remove', label: '删除会话', icon: 'fa fa-trash-o' },
    { name: 'remark', label: '修改备注', icon: 'fa fa-pencil' },
]

const onActiveContextmenu = (type: string, menu: any, el: MouseEvent) => {
    if (type == 'session') {
        sessionContextMenus[0].label = menu.top ? '取消置顶' : '置顶会话'
    } else {
        touristContextMenus[0].label = menu.status == 'await' ? '接入会话' : '强制对话'
    }

    kefu.activeSession(type, menu)
    kefu.state.contextMenuType = type

    const { clientX, clientY } = el
    contextmenuRef.value.onShowContextmenu(menu, {
        x: clientX,
        y: clientY,
    })
}
const onActiveContextmenuItem = (item: ContextMenuItemClickEmitArg) => {
    const { name, sourceData } = item
    if (!sourceData) return

    if (name == 'remark') {
        kefu.state.activeOptTab = 'base'
        nextTick(() => {
            userNicknameRef.value?.focus()
        })
        return
    } else if (name == 'dialog-force') {
        kefu.addSession(sourceData.id)
        return
    } else if (name == 'transfer') {
        kefu.state.transfer.show = true
        return
    }
    kefu.socketSend({
        id: sourceData.id,
        operate: name,
        pathInfo: 'worker/kefu.Wsession/operates',
    })
}

const onCsrStatusChange = (status: string) => {
    if (status == kefu.state.userInfo.status) return

    if ('offline' == status) {
        kefu.toggleSwitch(false)
    } else if ('online' == status && kefu.state.userInfo.status == 'offline') {
        kefu.toggleSwitch(true)
    } else {
        kefu.socketSend({
            status: status,
            pathInfo: 'worker/kefu.WsIndex/changeStatus',
        })
    }
}

const onAddSession = () => {
    kefu.state.sessionDialog.searchDialog = true
    setTimeout(() => {
        searchKeywordRef.value?.focus()
    }, 200)
}

const onSendSearch = debounce((type: string) => {
    kefu.state.sessionDialog.searchData = []
    kefu.state.sessionDialog.searchDataPage = 1

    const keyword = type == 'session' ? kefu.state.sessionDialog.searchSessionKeyword : state.searchDialogKeyword
    kefu.state.sessionDialog.searchSession = type == 'session' && keyword ? true : false
    if (!keyword) {
        return
    }

    kefu.socketSend({
        type: type,
        keyword: keyword,
        pathInfo: 'worker/kefu.Wsession/search',
    })
}, 300)

const onBaseInfoFormChange = (field: string) => {
    if (!kefu.state.baseInfoForm.id) return
    kefu.socketSend({
        id: kefu.state.baseInfoForm.id,
        field: field,
        sessionId: kefu.state.activeSession,
        value: kefu.state.baseInfoForm[field],
        pathInfo: 'worker/kefu.WsMixed/changeUserBaseInfo',
    })
}

const onOptChange = (name: TabPaneName) => {
    kefu.state.trajectorys.page = 1
    kefu.state.trajectorys.nextPage = true
    if (name == 'trajectory') {
        kefu.getTrajectoryTabData()
    } else if (name == 'kbs') {
        kefu.getKbsTabData()
    }
}

const onTransfer = () => {
    if (!kefu.state.transfer.csrId) {
        kefu.showTip('请选择要转接的客服代表', 'warning')
        return
    }

    kefu.state.transfer.loading = true
    kefu.socketSend({
        id: kefu.state.activeSession,
        csrId: kefu.state.transfer.csrId,
        operate: 'transfer',
        pathInfo: 'worker/kefu.Wsession/operates',
    })
}

const onMatchInput = debounce(() => {
    kefu.getKbsTabData()
}, 300)

const onSessionScroll = debounce(() => {
    contextmenuRef.value.onHideContextmenu()
}, 300)

const onTrajectoryScroll = debounce((e: Event) => {
    if (!e) return
    const target = e.target as HTMLDivElement

    if (target.scrollHeight - target.offsetHeight - target.scrollTop < 1) {
        kefu.state.trajectorys.page++
        kefu.getTrajectoryTabData()
    }
}, 300)

const getTrajectoryType = (trajectory: anyObj) => {
    if (trajectory.title == '访问') {
        return 'primary'
    } else {
        return 'success'
    }
}

const getTrajectoryContent = (trajectory: anyObj) => {
    if (trajectory.title == '访问') {
        return trajectory.title + ' ' + trajectory.url
    } else {
        return trajectory.title + ' ' + trajectory.details
    }
}

const onSendKb = (answer: string) => {
    kefu.state.messageInputValue += answer
    kefu.messageInputFocus()
}
</script>

<style scoped lang="scss">
:deep(.session-dialog) {
    .el-dialog__body {
        padding-top: 10px;
        padding-bottom: 26px;
        .dialog-session-search-box {
            height: 400px;
            .dialog-session-search {
                display: flex;
                align-items: center;
                justify-content: space-between;
                .dialog-search-left {
                    margin-right: 15px;
                }
            }
            .opts-session-list {
                display: block;
                margin-top: 10px;
                overflow-y: auto;
                overflow-x: hidden;
                height: calc(100% - 50px);
                .session-item {
                    float: left;
                    width: 50%;
                    .session-info {
                        .other {
                            margin-top: 4px;
                        }
                    }
                }
            }
        }
    }
}
.height-100 {
    height: 100%;
}
.await-response-loading {
    margin-left: 10px;
}
.session-item {
    display: flex;
    align-items: center;
    padding: 12px 14px;
    user-select: none;
    cursor: pointer;
    .avatar {
        width: 40px;
        height: 40px;
        border-radius: 50%;
    }
    .session-info {
        width: calc(100% - 40px);
        padding-left: 8px;
        .nickname,
        .title-box {
            display: block;
            overflow: hidden;
            text-overflow: ellipsis;
            white-space: nowrap;
            .nickname {
                font-size: 14px;
                font-weight: bold;
            }
        }
        .title-box {
            display: flex;
            justify-content: space-between;
            align-items: center;
            height: 20px;
            line-height: 20px;
            .date-time {
                font-size: 12px;
                color: var(--el-color-info);
            }
        }
        .other {
            font-size: 13px;
            overflow: hidden;
            text-overflow: ellipsis;
            white-space: nowrap;
            height: 20px;
            line-height: 20px;
        }
    }
    &:hover {
        background-color: #f4f4f5;
    }
}
.session-item.session-top {
    background: #f8f9f9;
}
.session-item.active {
    background: #f4f4f5;
}
.session-item.session-top.active {
    background-color: #eaeaea;
}

.my-status {
    display: flex;
    align-items: center;
    .status-dot {
        font-size: 22px;
        line-height: 22px;
        padding-bottom: 2px;
    }
    .status-text {
        padding-left: 4px;
        padding-right: 2px;
        font-size: 12px;
        color: var(--el-text-color-regular);
    }
}

.chat-col-box {
    color: var(--el-text-color-primary);
    height: 100%;
    border-radius: var(--el-border-radius-base);
    overflow: hidden;
}
.left-box {
    background-color: #fff;
    .csr-box {
        border-bottom: 1px solid var(--el-border-color-extra-light);
        .csr-info {
            .nickname {
                padding-left: 1px;
            }
        }
        &:hover {
            background-color: #fff;
        }
    }
    .tourist-list {
        display: block;
        height: calc(100% - 65px);
        overflow-y: auto;
        overflow-x: hidden;
        .tourist-item {
            .session-info {
                width: 100%;
                padding-left: 0;
            }
        }
    }
}
.session-row {
    .session-list {
        border-top-left-radius: var(--el-border-radius-base);
        border-bottom-left-radius: var(--el-border-radius-base);
        background-color: #fff;
        .session-search {
            display: flex;
            align-items: center;
            height: 50px;
            position: relative;
            .search-left {
                height: 24px;
                width: calc(100% - 34px);
                padding-left: 15px;
            }
            .search-right {
                display: flex;
                align-items: center;
                justify-content: center;
                width: 24px;
                height: 24px;
                margin: 0 8px;
                margin-right: 12px;
                &:hover {
                    background-color: #f4f4f5;
                }
            }
            .search-session-done {
                position: absolute;
                top: 50px;
                width: calc(100% - 20px);
                max-height: 480px;
                z-index: 1057;
                overflow-y: auto;
                overflow-x: hidden;
                box-shadow: 0 0 10px rgba(0, 0, 0, 0.2);
                border-radius: 3px;
                background-color: var(--el-color-white);
            }
        }
        .sessions {
            height: calc(100% - 50px);
            overflow-y: auto;
            overflow-x: hidden;
            .session-item {
                .avatar {
                    border-radius: 6px;
                }
                .session-info {
                    .badge {
                        display: inline-flex;
                        justify-content: center;
                        align-items: center;
                        padding: 0 5px;
                        min-height: 16px;
                        font-size: 12px;
                        line-height: 12px;
                        background: var(--el-color-danger);
                        border-radius: 50%;
                        color: #fff;
                        white-space: nowrap;
                    }
                }
            }
        }
    }
    .session-window {
        border-top-right-radius: var(--el-border-radius-base);
        border-bottom-right-radius: var(--el-border-radius-base);
        background-color: #fbfbfb;
        .session-header {
            display: flex;
            align-items: center;
            height: 50px;
            border-bottom: 1px solid var(--el-border-color-extra-light);
            .title {
                padding-left: 10px;
                font-weight: bold;
                &:hover {
                    text-decoration: underline;
                    cursor: pointer;
                }
            }
        }
        .window-records {
            position: relative;
            height: calc(100% - 50px);
        }
    }
}
.right-box {
    background-color: #fff;
    .operate-tabs {
        padding: 0 5px;
        :deep(.el-tabs__content) {
            height: calc(100% - 60px);
        }
        .operate-tabs-pane {
            height: 100%;
            padding: 0 5px 0 10px;
            overflow-y: auto;
            overflow-x: hidden;
        }
        .trajectory-timeline {
            padding-left: 6px;
            :deep(.el-timeline-item__content) {
                word-wrap: break-word;
                word-break: break-all;
            }
        }
        .kbs-list {
            margin-top: 5px;
            .kbs-item {
                color: var(--el-text-color-primary);
                padding: 5px 0;
                .kbs-title {
                    font-size: 13px;
                    font-weight: bold;
                }
                .kbs-content-box {
                    display: flex;
                    align-items: center;
                    justify-content: space-between;
                    .kbs-content {
                        font-size: 13px;
                        overflow: hidden;
                        text-overflow: ellipsis;
                        display: -webkit-box;
                        -webkit-box-orient: vertical;
                        -webkit-line-clamp: 3;
                        line-clamp: 3;
                        line-height: 16px;
                        max-height: 48px;
                        margin: 5px 5px 0 0;
                    }
                    .send-button {
                        width: 48px;
                    }
                }
            }
        }
    }
}
.status-busy,
.status-await {
    color: #ff647e !important;
}
.status-invite {
    color: var(--el-color-info) !important;
}
.status-offline {
    color: #999999 !important;
}
.status-online {
    color: #21e589 !important;
}
.status-invisible {
    color: #ff9c4e !important;
}
</style>
